import java.util.Random;
import java.util.concurrent.Phaser;

public class PhaserTest {
    public static void main(String[] args) throws InterruptedException {
        // 导游
        Phaser phaser = new TouristGuide();
        // 游客
        Tourist[] tourists = new Tourist[5];
        for (int i = 0; i < tourists.length; i++) {
            tourists[i] = new Tourist(phaser, "游客" + i);
            // 注册 Phaser 等待的线程数，执行一次等待线程数 +1
            phaser.register();
        }

        // 每个游客自行活动..
        for (int i = 0; i < tourists.length; i++) {
            // 执行任务
            new Thread(tourists[i]).start();
        }
    }

    static class Tourist implements Runnable {
        private final Phaser phaser;

        private String name;

        public Tourist(Phaser phaser, String name) {
            this.phaser = phaser;
            this.name = name;
        }

        @Override
        public void run() {
            System.out.println(this.name + " | 到了");
            phaser.arriveAndAwaitAdvance();
            try {
                Thread.sleep(new Random().nextInt(5) * 1000);
                System.out.println(this.name + " | 拍完照片了...");
                phaser.arriveAndAwaitAdvance();
                Thread.sleep(new Random().nextInt(5) * 1000);
                System.out.println(this.name + " | 拍完照片了...");
                phaser.arriveAndAwaitAdvance();
                Thread.sleep(new Random().nextInt(5) * 1000);
                System.out.println(this.name + ":\"拍啥拍，赶紧去看皇帝皇后睡觉吧\"");
                phaser.arriveAndAwaitAdvance();
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }
    }

    // Phaser 每个阶段完成之后的事件通知.  (===> 导游）
    static class TouristGuide extends Phaser {
        /**
         * 每个阶段执行完之后的回调
         */
        @Override
        protected boolean onAdvance(int phase, int registeredParties) {
            switch (phase) {
                case 0 -> {
                    System.out.println("首先，这里我看到的是：太和殿, xxx(巴啦啦，说一通历史), 大家先去拍照, 拍完照到我这里集合, 咱们去下一个殿");
                    return false;
                }
                case 1-> {
                    System.out.println("那么，这里我看到的是：中和殿, xxx(巴啦啦，说一通历史), 大家先去拍照, 拍完照到我这里集合, 咱们去下一个殿");
                    return false;
                }
                case 2 -> {
                    System.out.println("最后，这里我看到的是：保和殿, xxx(巴啦啦，说一通历史), 大家先去拍照, 拍完照到我这里集合, 咱们去看看皇帝和皇后睡觉的地方");
                    return false;
                }
                default -> {
                    return true;
                }
            }
        }
    }
}